<?php

namespace WebModule;

use ApplicationsModule\PeopleModule\PeopleManagement;
use Celebrio\AccessControl\UserManagement;
use \Albireo\OAuth\OAuthClient;
use Albireo\Forms\AlbireoForm;
use \Facebook;

/**
 * Sign In Page presenter.
 *
 * @author     Albireo Solutions
 * @package    Kernel
 */
class FacebookAppPresenter extends BasePresenter {

    private $facebook_sdk;

    /** @persistent */
    public $search_name = "";

    public function __construct() {
        $oAuthClient = new OAuthClient(OAuthClient::FB);
        $credentials = $oAuthClient->getCredentials();
        $appInfo = array(
            'appId' => $credentials["key"],
            'secret' => $credentials["secret"],
        );

        $this->facebook_sdk = new \Facebook($appInfo);
    }

    public function actionDefault() {
        
    }

    public function actionAppAccessToken() {
        $token = $this->facebook_sdk->getAccessToken();
        $this->getTemplate()->token = $token;
    }

    /**
     * Asks the user for the permission. The method ends by redirect to FB dialog.
     *
     * @throws \Exception
     * @return void
     */
    public function actionRequest() {

        $oAuthClient = new OAuthClient(OAuthClient::FB);
        $scope = array("offline_access", "email");
        $requestTokenInfo = $oAuthClient->getRequestTokenUri($this->link("//authorized"), $scope);
        $this->redirectUri($requestTokenInfo);
    }

    public function actionAuthorized(/* polymorphic */) {
        $params = $this->getHttpRequest()->getQuery();
        if (array_key_exists("error", $params)) {
            // the user has denied the access, fuck him
//            \Nette\Debug::dump($params);
            throw new \Exception("an error occured, probably the user has denied access to his account");
        } elseif (array_key_exists("code", $params)) {

            $access_token = $this->facebook_sdk->getAccessTokenFromCode($params["code"]);
            $this->facebook_sdk->setAccessToken($access_token);
            $user = $this->facebook_sdk->api("/me"); // we assume the user is logged in


            $fb_user_m = new FacebookUserManager();

            $params["access_token"] = $access_token;
            $fb_user_m->addUser($user, $params);

            $this->flashMessage("We've got you. You can run but never hide. We know your name, your family, your hobbies, " . $user['first_name'] . ". And the same about your friends...");
            $this->flashMessage("use this if you want to get people lookup running: $access_token");

            $this->redirect("default");
        }
    }

    public function renderFriends() {
        $query = \dibi::select(array("first_name_person", "last_name_person", "id_person"))->from("people")->where("id_user=%i and connection_approved=%i", $this->getUser()->getIdentity()->id, 0);
        
        $friends = $query->execute()->fetchAll();
        $this->template->friends = $friends;
    }
    
    public function actionApproveFriend($id) {
        $query = \dibi::update("people", array("connection_approved" => 1))->where(array("id_person" => $id, "id_user" => $this->getUser()->getIdentity()->id));
        $query->execute();
        $this->redirect("friends");
    }
    
    public function createComponentFindFriends() {
        $form = new AlbireoForm();
        $form->addText("name", _("Name"));
        $form->addSubmit("submitted", _("Send"));

        $form->onSubmit[] = callback($this, "findFriendsSubmitted");

        return $form;
    }

    public function findFriendsSubmitted($form) {
        $values = $form->values;
        $name = $values["name"];
        if (substr_count($name, "guest") !== 0) {
            $this->search_name = "Nobody found.";
            return;
        }

        //if there is more spaces (e.g. Bozena Svobodova Nemcova)
        //we take first word and make second word as SvobodovaNemcova
        //but this is useles as I tried.
        if (substr_count($name, " ") > 1) {
            $name_sur = explode(" ", $name);
            $first = $name_sur[0];
            $second = "";
            foreach ($name_sur as $c => $name_to_append) {
                if ($c < 1)
                    continue;
                $second .= $name_to_append;
            }

            $name = $first . " " . $second;
        }

        $this->search_name = $name;
        $this->invalidateControl("existing");
    }

    public function createComponentPermissionScope() {
        $form = new AlbireoForm();

        if ($this->search_name == null) {
            return $form;
        }
        $um = new UserManagement();
        $dataSource = $um->getFilteredUsersDataSourceOnlyName($this->search_name);
        $existing = $dataSource->fetchAll();
        if (empty($existing)) {
            return $form;
        }
        $result = array();

        foreach ($existing as $e) {
            $form->addCheckbox("user" . $e["id"], $e["first_name"] . " " . $e["last_name"]);
            //$result[] = array("first_name" => $e["first_name"], "last_name" => $e["last_name"], "id_user" => $e["id"]);
        }
        $form->addSubmit("submitted", _("Send"));
        $form->addCheckbox("user_about_me", _("Informations about yourself"))->setDefaultValue(true);
        $form->addCheckbox("friends_about_me", _("Informations about your friends"))->setDefaultValue(true);
        $form->addCheckbox("email", "Your email")->setDefaultValue(true);
        $form->addCheckbox("user_activities", _("Your activities"))->setDefaultValue(true);
        $form->addCheckbox("friends_activities", _("Friends activities"))->setDefaultValue(true);
        $form->addCheckbox("user_birthday", _("Your birthday"))->setDefaultValue(true);
        $form->addCheckbox("friends_birthday", _("Friends birthday"))->setDefaultValue(true);
        $form->addCheckbox("user_hometown", _("Your hometown"))->setDefaultValue(true);
        $form->addCheckbox("friends_hometown", _("Friends hometown"))->setDefaultValue(true);
        $form->addCheckbox("user_interests", _("Your interests"))->setDefaultValue(true);
        $form->addCheckbox("friends_interests", _("Friends interests"))->setDefaultValue(true);
        $form->addCheckbox("user_photos", _("Your photos"))->setDefaultValue(true);
        $form->addCheckbox("friends_photos", _("Friends photos"))->setDefaultValue(true);
        $form->addCheckbox("user_relationships", _("Your relationships"))->setDefaultValue(true);
        $form->addCheckbox("friends_relationships", _("Friends relationships"))->setDefaultValue(true);
        $form->addCheckbox("user_status", _("Your status"))->setDefaultValue(true);
        $form->addCheckbox("friends_status", _("Friends status"))->setDefaultValue(true);
        $form->addCheckbox("user_videos", "Your videos")->setDefaultValue(true);
        $form->addCheckbox("friends_videos", "Friends videos")->setDefaultValue(true);
        
        $form->addCheckbox("offline_access", "offline access")->setDefaultValue(TRUE);

        $form->onSubmit[] = callback($this, "permissionScopeSubmitted");

        return $form;
    }

    public function permissionScopeSubmitted($form) {
        $values = $form->values;
        $users_to_be_added = array();
        $permission_scope = array();
        foreach ($values as $name => $value) {
            //if name is like user25 and value is true
            if (preg_match("/^user\d/", $name) && $value === TRUE) {
                $this->isWanted($name, $users_to_be_added);
            } elseif ($value === TRUE) {
                $permission_scope[] = $name;
            }
        }

        $oAuthClient = new OAuthClient(OAuthClient::FB);
        $requestTokenInfo = $oAuthClient->getRequestTokenUri($this->link("//authorized"), $permission_scope, ",", $users_to_be_added);
        $this->redirectUri($requestTokenInfo);
        
    }

        /**
         * This function just takes the $user_name and replace "user" part and
         * add the number (which is id of user) to given array.
         * @param type $user_name (e.g. user70)
         * @param array $users reference to array of users we want to add user in.
         */
        private function isWanted($user_name, &$users) {
            is_numeric($number = preg_replace("/user/", "", $user_name)) ? $users[] = (int) $number : false;
        }

        public function renderGetInfo() {
            $a = \dibi::query("select [access_token] from [fb_users_approved]")->fetchSingle();
            $this->facebook_sdk->setAccessToken($a);
        }
    }